// UtilityFunction.cpp: implementation of the UtilityFunction class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "UtilityFunction.h"

DWORD FLT2DWORD( FLOAT f )
{
	return *( (DWORD*)&f );
}

BOOL CreateRing( PDIRECT3DDEVICE8 pDevice, FLOAT fr, FLOAT fR, DWORD dwSegCount, PDIRECT3DVERTEXBUFFER8* ppvb )
{
	DWORD		dwVertexCount = 2*(dwSegCount + 1);

	if( FAILED( pDevice->CreateVertexBuffer( dwVertexCount*sizeof(LVERTEX), 0, FVF_LVERTEX, D3DPOOL_DEFAULT, ppvb ) ) )
		return FALSE;

	PLVERTEX	pVertices;
	FLOAT		fAngle = 0.0f;
	FLOAT		fDelta = H_2PI/(FLOAT)dwSegCount;
	DWORD		index = 0;

	(*ppvb)->Lock( 0, 0, (LPBYTE*)&pVertices, 0 );

	pVertices[index++] = LVERTEX( fr*cosf(fAngle), fr*sinf(fAngle), 0, 0xffffff, 0.0f, 1.0f );
	pVertices[index++] = LVERTEX( fR*cosf(fAngle), fR*sinf(fAngle), 0, 0xffffff, 0.0f, 0.0f );

	fAngle += fDelta;
	pVertices[index++] = LVERTEX( fr*cosf(fAngle), fr*sinf(fAngle), 0, 0xffffff, fAngle/H_2PI, 1.0f );

	for( DWORD i = 1 ; i < dwSegCount ; i++ )
	{
		pVertices[index++] = LVERTEX( fR*cosf(fAngle), fR*sinf(fAngle), 0, 0xffffff, fAngle/H_2PI, 0.0f );
		fAngle += fDelta;
		pVertices[index++] = LVERTEX( fr*cosf(fAngle), fr*sinf(fAngle), 0, 0xffffff, fAngle/H_2PI, 1.0f );
	}

	pVertices[index++] = LVERTEX( fR*cosf(fAngle), fR*sinf(fAngle), 0, 0xffffff, fAngle/H_2PI, 0.0f );	

	(*ppvb)->Unlock();
		
	return TRUE;
}

BOOL CreateCube( PDIRECT3DDEVICE8 pDevice, FLOAT fA, PDIRECT3DVERTEXBUFFER8* ppvb, DWORD dwColor )
{
	if( FAILED( pDevice->CreateVertexBuffer( 36*sizeof(LVERTEX), 0, FVF_LVERTEX, D3DPOOL_DEFAULT, ppvb ) ) )
		return FALSE;

	PLVERTEX				pVertices;
	FLOAT					fSize = 0.5f*fA;

	(*ppvb)->Lock( 0, 0, (LPBYTE*)&pVertices, 0 );

	pVertices[ 0] = LVERTEX( -fSize, -fSize, -fSize, dwColor, 0.0f, 1.0f );
	pVertices[ 1] = LVERTEX( -fSize,  fSize, -fSize, dwColor, 0.0f, 0.0f );
	pVertices[ 2] = LVERTEX(  fSize, -fSize, -fSize, dwColor, 1.0f, 1.0f );
	pVertices[ 3] = LVERTEX(  fSize, -fSize, -fSize, dwColor, 1.0f, 1.0f );
	pVertices[ 4] = LVERTEX( -fSize,  fSize, -fSize, dwColor, 0.0f, 0.0f );
	pVertices[ 5] = LVERTEX(  fSize,  fSize, -fSize, dwColor, 1.0f, 0.0f );

	pVertices[ 6] = LVERTEX( -fSize, -fSize,  fSize, dwColor, 1.0f, 1.0f );
	pVertices[ 7] = LVERTEX( -fSize,  fSize,  fSize, dwColor, 1.0f, 0.0f );
	pVertices[ 8] = LVERTEX(  fSize, -fSize,  fSize, dwColor, 0.0f, 1.0f );
	pVertices[ 9] = LVERTEX(  fSize, -fSize,  fSize, dwColor, 0.0f, 1.0f );
	pVertices[10] = LVERTEX( -fSize,  fSize,  fSize, dwColor, 1.0f, 0.0f );
	pVertices[11] = LVERTEX(  fSize,  fSize,  fSize, dwColor, 0.0f, 0.0f );

	pVertices[12] = LVERTEX(  fSize, -fSize, -fSize, dwColor, 1.0f, 1.0f );
	pVertices[13] = LVERTEX(  fSize,  fSize, -fSize, dwColor, 1.0f, 0.0f );
	pVertices[14] = LVERTEX(  fSize, -fSize,  fSize, dwColor, 0.0f, 1.0f );
	pVertices[15] = LVERTEX(  fSize, -fSize,  fSize, dwColor, 0.0f, 1.0f );
	pVertices[16] = LVERTEX(  fSize,  fSize, -fSize, dwColor, 1.0f, 0.0f );
	pVertices[17] = LVERTEX(  fSize,  fSize,  fSize, dwColor, 0.0f, 0.0f );

	pVertices[18] = LVERTEX( -fSize, -fSize, -fSize, dwColor, 0.0f, 1.0f );
	pVertices[19] = LVERTEX( -fSize,  fSize, -fSize, dwColor, 0.0f, 0.0f );
	pVertices[20] = LVERTEX( -fSize, -fSize,  fSize, dwColor, 1.0f, 1.0f );
	pVertices[21] = LVERTEX( -fSize, -fSize,  fSize, dwColor, 1.0f, 1.0f );
	pVertices[22] = LVERTEX( -fSize,  fSize, -fSize, dwColor, 0.0f, 0.0f );
	pVertices[23] = LVERTEX( -fSize,  fSize,  fSize, dwColor, 1.0f, 0.0f );

	pVertices[24] = LVERTEX( -fSize,  fSize, -fSize, dwColor, 0.0f, 1.0f );
	pVertices[25] = LVERTEX( -fSize,  fSize,  fSize, dwColor, 0.0f, 0.0f );
	pVertices[26] = LVERTEX(  fSize,  fSize, -fSize, dwColor, 1.0f, 1.0f );
	pVertices[27] = LVERTEX(  fSize,  fSize, -fSize, dwColor, 1.0f, 1.0f );
	pVertices[28] = LVERTEX( -fSize,  fSize,  fSize, dwColor, 0.0f, 0.0f );
	pVertices[29] = LVERTEX(  fSize,  fSize,  fSize, dwColor, 1.0f, 0.0f );

	pVertices[30] = LVERTEX( -fSize, -fSize, -fSize, dwColor, 0.0f, 1.0f );
	pVertices[31] = LVERTEX( -fSize, -fSize,  fSize, dwColor, 0.0f, 0.0f );
	pVertices[32] = LVERTEX(  fSize, -fSize, -fSize, dwColor, 1.0f, 1.0f );
	pVertices[33] = LVERTEX(  fSize, -fSize, -fSize, dwColor, 1.0f, 1.0f );
	pVertices[34] = LVERTEX( -fSize, -fSize,  fSize, dwColor, 0.0f, 0.0f );
	pVertices[35] = LVERTEX(  fSize, -fSize,  fSize, dwColor, 1.0f, 0.0f );

	(*ppvb)->Unlock();

	return TRUE;
}

BOOL CreateUnlitCube( PDIRECT3DDEVICE8 pDevice, FLOAT fA, PDIRECT3DVERTEXBUFFER8* ppvb )
{
	if( FAILED( pDevice->CreateVertexBuffer( 36*sizeof(VERTEX), 0, FVF_VERTEX, D3DPOOL_DEFAULT, ppvb ) ) )
		return FALSE;

	PVERTEX					pVertices;
	FLOAT					fSize = 0.5f*fA;

	(*ppvb)->Lock( 0, 0, (LPBYTE*)&pVertices, 0 );

	pVertices[ 0] = VERTEX( -fSize, -fSize, -fSize,  0,  0, -1, 0.0f, 1.0f );
	pVertices[ 1] = VERTEX( -fSize,  fSize, -fSize,  0,  0, -1, 0.0f, 0.0f );
	pVertices[ 2] = VERTEX(  fSize, -fSize, -fSize,  0,  0, -1, 1.0f, 1.0f );
	pVertices[ 3] = VERTEX(  fSize, -fSize, -fSize,  0,  0, -1, 1.0f, 1.0f );
	pVertices[ 4] = VERTEX( -fSize,  fSize, -fSize,  0,  0, -1, 0.0f, 0.0f );
	pVertices[ 5] = VERTEX(  fSize,  fSize, -fSize,  0,  0, -1, 1.0f, 0.0f );

	pVertices[ 6] = VERTEX( -fSize, -fSize,  fSize,  0,  0,  1, 1.0f, 1.0f );
	pVertices[ 7] = VERTEX( -fSize,  fSize,  fSize,  0,  0,  1, 1.0f, 0.0f );
	pVertices[ 8] = VERTEX(  fSize, -fSize,  fSize,  0,  0,  1, 0.0f, 1.0f );
	pVertices[ 9] = VERTEX(  fSize, -fSize,  fSize,  0,  0,  1, 0.0f, 1.0f );
	pVertices[10] = VERTEX( -fSize,  fSize,  fSize,  0,  0,  1, 1.0f, 0.0f );
	pVertices[11] = VERTEX(  fSize,  fSize,  fSize,  0,  0,  1, 0.0f, 0.0f );

	pVertices[12] = VERTEX(  fSize, -fSize, -fSize,  0,  0, -1, 1.0f, 1.0f );
	pVertices[13] = VERTEX(  fSize,  fSize, -fSize,  0,  0, -1, 1.0f, 0.0f );
	pVertices[14] = VERTEX(  fSize, -fSize,  fSize,  1,  0,  0, 0.0f, 1.0f );
	pVertices[15] = VERTEX(  fSize, -fSize,  fSize,  1,  0,  0, 0.0f, 1.0f );
	pVertices[16] = VERTEX(  fSize,  fSize, -fSize,  0,  0, -1, 1.0f, 0.0f );
	pVertices[17] = VERTEX(  fSize,  fSize,  fSize,  1,  0,  0, 0.0f, 0.0f );

	pVertices[18] = VERTEX( -fSize, -fSize, -fSize,  0,  0, -1, 0.0f, 1.0f );
	pVertices[19] = VERTEX( -fSize,  fSize, -fSize,  0,  0, -1, 0.0f, 0.0f );
	pVertices[20] = VERTEX( -fSize, -fSize,  fSize, -1,  0,  0, 1.0f, 1.0f );
	pVertices[21] = VERTEX( -fSize, -fSize,  fSize, -1,  0,  0, 1.0f, 1.0f );
	pVertices[22] = VERTEX( -fSize,  fSize, -fSize,  0,  0, -1, 0.0f, 0.0f );
	pVertices[23] = VERTEX( -fSize,  fSize,  fSize, -1,  0,  0, 1.0f, 0.0f );

	pVertices[24] = VERTEX( -fSize,  fSize, -fSize,  0,  0, -1, 0.0f, 1.0f );
	pVertices[25] = VERTEX( -fSize,  fSize,  fSize,  0,  1,  0, 0.0f, 0.0f );
	pVertices[26] = VERTEX(  fSize,  fSize, -fSize,  0,  0, -1, 1.0f, 1.0f );
	pVertices[27] = VERTEX(  fSize,  fSize, -fSize,  0,  0, -1, 1.0f, 1.0f );
	pVertices[28] = VERTEX( -fSize,  fSize,  fSize,  0,  1,  0, 0.0f, 0.0f );
	pVertices[29] = VERTEX(  fSize,  fSize,  fSize,  0,  1,  0, 1.0f, 0.0f );

	pVertices[30] = VERTEX( -fSize, -fSize, -fSize,  0,  0, -1, 0.0f, 1.0f );
	pVertices[31] = VERTEX( -fSize, -fSize,  fSize,  0, -1,  0, 0.0f, 0.0f );
	pVertices[32] = VERTEX(  fSize, -fSize, -fSize,  0,  0, -1, 1.0f, 1.0f );
	pVertices[33] = VERTEX(  fSize, -fSize, -fSize,  0,  0, -1, 1.0f, 1.0f );
	pVertices[34] = VERTEX( -fSize, -fSize,  fSize,  0, -1,  0, 0.0f, 0.0f );
	pVertices[35] = VERTEX(  fSize, -fSize,  fSize,  0, -1,  0, 1.0f, 0.0f );

	(*ppvb)->Unlock();

	return TRUE;
}

VOID CreateCube( PLVERTEX pVertices, FLOAT fA, he3d_CVector& vCenter, DWORD dwColor )
{
	FLOAT					fSize = 0.5f*fA;	

	pVertices[ 0] = LVERTEX( he3d_CVector( -fSize, -fSize, -fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[ 1] = LVERTEX( he3d_CVector( -fSize,  fSize, -fSize ) + vCenter, dwColor, 0.0f, 0.0f );
	pVertices[ 2] = LVERTEX( he3d_CVector(  fSize, -fSize, -fSize ) + vCenter, dwColor, 1.0f, 1.0f );	
	pVertices[ 3] = LVERTEX( he3d_CVector(  fSize, -fSize, -fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[ 4] = LVERTEX( he3d_CVector( -fSize,  fSize, -fSize ) + vCenter, dwColor, 0.0f, 0.0f );	
	pVertices[ 5] = LVERTEX( he3d_CVector(  fSize,  fSize, -fSize ) + vCenter, dwColor, 1.0f, 0.0f );	

	pVertices[ 6] = LVERTEX( he3d_CVector( -fSize, -fSize,  fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[ 7] = LVERTEX( he3d_CVector(  fSize, -fSize,  fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[ 8] = LVERTEX( he3d_CVector( -fSize,  fSize,  fSize ) + vCenter, dwColor, 1.0f, 0.0f );
	pVertices[ 9] = LVERTEX( he3d_CVector(  fSize, -fSize,  fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[10] = LVERTEX( he3d_CVector(  fSize,  fSize,  fSize ) + vCenter, dwColor, 0.0f, 0.0f );
	pVertices[11] = LVERTEX( he3d_CVector( -fSize,  fSize,  fSize ) + vCenter, dwColor, 1.0f, 0.0f );	


	pVertices[12] = LVERTEX( he3d_CVector(  fSize, -fSize, -fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[14] = LVERTEX( he3d_CVector(  fSize, -fSize,  fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[13] = LVERTEX( he3d_CVector(  fSize,  fSize, -fSize ) + vCenter, dwColor, 1.0f, 0.0f );
	pVertices[15] = LVERTEX( he3d_CVector(  fSize, -fSize,  fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[17] = LVERTEX( he3d_CVector(  fSize,  fSize,  fSize ) + vCenter, dwColor, 0.0f, 0.0f );
	pVertices[16] = LVERTEX( he3d_CVector(  fSize,  fSize, -fSize ) + vCenter, dwColor, 1.0f, 0.0f );
	

	pVertices[18] = LVERTEX( he3d_CVector( -fSize, -fSize, -fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[20] = LVERTEX( he3d_CVector( -fSize,  fSize, -fSize ) + vCenter, dwColor, 0.0f, 0.0f );
	pVertices[19] = LVERTEX( he3d_CVector( -fSize, -fSize,  fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[21] = LVERTEX( he3d_CVector( -fSize, -fSize,  fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[23] = LVERTEX( he3d_CVector( -fSize,  fSize, -fSize ) + vCenter, dwColor, 0.0f, 0.0f );
	pVertices[22] = LVERTEX( he3d_CVector( -fSize,  fSize,  fSize ) + vCenter, dwColor, 1.0f, 0.0f );


	pVertices[24] = LVERTEX( he3d_CVector( -fSize,  fSize, -fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[26] = LVERTEX( he3d_CVector(  fSize,  fSize, -fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[25] = LVERTEX( he3d_CVector( -fSize,  fSize,  fSize ) + vCenter, dwColor, 0.0f, 0.0f );	
	pVertices[27] = LVERTEX( he3d_CVector(  fSize,  fSize, -fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[29] = LVERTEX( he3d_CVector(  fSize,  fSize,  fSize ) + vCenter, dwColor, 1.0f, 0.0f );
	pVertices[28] = LVERTEX( he3d_CVector( -fSize,  fSize,  fSize ) + vCenter, dwColor, 0.0f, 0.0f );	


	pVertices[30] = LVERTEX( he3d_CVector( -fSize, -fSize, -fSize ) + vCenter, dwColor, 0.0f, 1.0f );
	pVertices[32] = LVERTEX( he3d_CVector( -fSize, -fSize,  fSize ) + vCenter, dwColor, 0.0f, 0.0f );
	pVertices[31] = LVERTEX( he3d_CVector(  fSize, -fSize, -fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[33] = LVERTEX( he3d_CVector(  fSize, -fSize, -fSize ) + vCenter, dwColor, 1.0f, 1.0f );
	pVertices[35] = LVERTEX( he3d_CVector( -fSize, -fSize,  fSize ) + vCenter, dwColor, 0.0f, 0.0f );
	pVertices[34] = LVERTEX( he3d_CVector(  fSize, -fSize,  fSize ) + vCenter, dwColor, 1.0f, 0.0f );
}

//=================================================================================================
// splines
//=================================================================================================

_FLOATKEY::_FLOATKEY() : t( 0.0f ), val( 0.0f )
{
}

_FLOATKEY::_FLOATKEY( FLOAT time, FLOAT value ) : t( time ), val( value )
{
}

_VECTORKEY::_VECTORKEY() : t( 0.0f ), val( 0.0f, 0.0f, 0.0f )
{
}

_VECTORKEY::_VECTORKEY( FLOAT time, he3d_CVector& v ) : t( time ), val( v )
{
}

_VECTORKEY::_VECTORKEY( FLOAT time, FLOAT x, FLOAT y, FLOAT z ) : t( time ), val( x, y, z )
{
}

VOID InitFloatSpline( DWORD dwKeysCount, PFLOATKEY pfkKeys )
{
	if( dwKeysCount <= 1 )
		return;

	FLOAT				delta1, delta2;	
	FLOAT				f1, f2;	

	for( DWORD i = 0 ; i < dwKeysCount ; i++ )
	{		
		delta1 = 0.5f;
		delta2 = 0.5f;

		if( i != dwKeysCount - 1 )		
			f1 = pfkKeys[i+1].val - pfkKeys[i].val;		

		if( i != 0 )		
			f2 = pfkKeys[i].val - pfkKeys[i-1].val;
		
		if( i == dwKeysCount - 1 )
			f1 = f2;

		if( i == 0 )
			f2 = f1;

		if( i != 0 && i != dwKeysCount - 1 )
		{
			delta1 = ( pfkKeys[i+1].t - pfkKeys[i].t )/( pfkKeys[i+1].t - pfkKeys[i-1].t );
			delta2 = ( pfkKeys[i].t - pfkKeys[i-1].t )/( pfkKeys[i+1].t - pfkKeys[i-1].t );
		}
		
		pfkKeys[i].t0 = delta1*( f1 + f2 );		
		pfkKeys[i].t1 = delta2*( f1 + f2 );
	}
}

FLOAT GetFloatSplineValue( FLOAT fT, DWORD dwKeysCount, PFLOATKEY pfkKeys )
{	
	if( dwKeysCount <= 1 )
		return pfkKeys[0].val;

	if( pfkKeys[0].t >= fT )
		return pfkKeys[0].val;

	if( pfkKeys[dwKeysCount-1].t <= fT )
		return pfkKeys[dwKeysCount-1].val;

	for( DWORD i = 0 ; i < dwKeysCount - 1  && pfkKeys[i+1].t < fT ; i++ );

	FLOAT					t, t2, t3;
	FLOAT					h[4];

	t = (fT - pfkKeys[i].t)/(pfkKeys[i+1].t - pfkKeys[i].t);	

	t2 = t*t;
	t3 = t2*t;	

	h[0] = 2*t3 - 3*t2 + 1;
	h[1] = -2*t3 + 3*t2;
	h[2] = t3 - 2*t2 + t;
	h[3] = t3 - t2;

	return h[0]*pfkKeys[i].val + h[1]*pfkKeys[i+1].val + h[2]*pfkKeys[i].t0 + h[3]*pfkKeys[i+1].t1;
}

VOID InitVectorSpline( DWORD dwKeysCount, PVECTORKEY pvkKeys )
{
	if( dwKeysCount <= 1 )
		return;

	FLOAT				delta1, delta2;	
	he3d_CVector		v1, v2;	

	for( DWORD i = 0 ; i < dwKeysCount ; i++ )
	{		
		delta1 = 0.5f;
		delta2 = 0.5f;

		if( i != dwKeysCount - 1 )		
			v1 = pvkKeys[i+1].val - pvkKeys[i].val;		

		if( i != 0 )		
			v2 = pvkKeys[i].val - pvkKeys[i-1].val;
		
		if( i == dwKeysCount - 1 )
			v1 = v2;

		if( i == 0 )
			v2 = v1;

		if( i != 0 && i != dwKeysCount - 1 )
		{
			delta1 = ( pvkKeys[i+1].t - pvkKeys[i].t )/( pvkKeys[i+1].t - pvkKeys[i-1].t );
			delta2 = ( pvkKeys[i].t - pvkKeys[i-1].t )/( pvkKeys[i+1].t - pvkKeys[i-1].t );
		}
		
		pvkKeys[i].t0 = delta1*( v1 + v2 );		
		pvkKeys[i].t1 = delta2*( v1 + v2 );
	}
}

he3d_CVector GetVectorSplineValue( FLOAT fT, DWORD dwKeysCount, PVECTORKEY pvkKeys )
{
	if( dwKeysCount <= 1 )
		return pvkKeys[0].val;

	if( pvkKeys[0].t >= fT )
		return pvkKeys[0].val;

	if( pvkKeys[dwKeysCount-1].t <= fT )
		return pvkKeys[dwKeysCount-1].val;

	for( DWORD i = 0 ; i < dwKeysCount - 1  && pvkKeys[i+1].t < fT ; i++ );

	FLOAT					t, t2, t3;
	FLOAT					h[4];

	t = (fT - pvkKeys[i].t)/(pvkKeys[i+1].t - pvkKeys[i].t);	

	t2 = t*t;
	t3 = t2*t;	

	h[0] = 2*t3 - 3*t2 + 1;
	h[1] = -2*t3 + 3*t2;
	h[2] = t3 - 2*t2 + t;
	h[3] = t3 - t2;

	return h[0]*pvkKeys[i].val + h[1]*pvkKeys[i+1].val + h[2]*pvkKeys[i].t0 + h[3]*pvkKeys[i+1].t1;
}

he3d_CVector Polar2Cartesian3d( FLOAT fRadius, FLOAT fAlpha, FLOAT fBeta )
{
	return he3d_CVector( fRadius*cosf(fAlpha)*sinf(fBeta), fRadius*cosf(fBeta), fRadius*sinf(fAlpha)*sinf(fBeta) );
}

VOID SetupMaterial( D3DMATERIAL8* d3dmat, DWORD dwDiffuse, DWORD dwAmbient )
{
	ZeroMemory( d3dmat, sizeof(D3DMATERIAL8) );

	d3dmat->Ambient.a = ( (FLOAT)( ( dwAmbient >> 24 )&0xff ) )/255.0f;
	d3dmat->Ambient.r = ( (FLOAT)( ( dwAmbient >> 16 )&0xff ) )/255.0f;
	d3dmat->Ambient.g = ( (FLOAT)( ( dwAmbient >>  8 )&0xff ) )/255.0f;
	d3dmat->Ambient.b = ( (FLOAT)( ( dwAmbient >>  0 )&0xff ) )/255.0f;

	d3dmat->Diffuse.a = ( (FLOAT)( ( dwDiffuse >> 24 )&0xff ) )/255.0f;
	d3dmat->Diffuse.r = ( (FLOAT)( ( dwDiffuse >> 16 )&0xff ) )/255.0f;
	d3dmat->Diffuse.g = ( (FLOAT)( ( dwDiffuse >>  8 )&0xff ) )/255.0f;
	d3dmat->Diffuse.b = ( (FLOAT)( ( dwDiffuse >>  0 )&0xff ) )/255.0f;
}

VOID SetupDirLight( D3DLIGHT8* d3dlit, he3d_CVector& dir, DWORD dwColor, FLOAT fRange, FLOAT fAtt0, FLOAT fAtt1, FLOAT fAtt2 )
{
	ZeroMemory( d3dlit, sizeof(D3DLIGHT8) );

	d3dlit->Type			= D3DLIGHT_DIRECTIONAL;

	d3dlit->Attenuation0	= fAtt0;
	d3dlit->Attenuation1	= fAtt1;
	d3dlit->Attenuation2	= fAtt2;

	d3dlit->Range			= fRange;

	d3dlit->Direction.x		= dir.x;
	d3dlit->Direction.y		= dir.y;
	d3dlit->Direction.z		= dir.z;

	d3dlit->Diffuse.a = ( (FLOAT)( ( dwColor >> 24 )&0xff ) )/255.0f;
	d3dlit->Diffuse.r = ( (FLOAT)( ( dwColor >> 16 )&0xff ) )/255.0f;
	d3dlit->Diffuse.g = ( (FLOAT)( ( dwColor >>  8 )&0xff ) )/255.0f;
	d3dlit->Diffuse.b = ( (FLOAT)( ( dwColor >>  0 )&0xff ) )/255.0f;
}

VOID SetupPointLight( D3DLIGHT8* d3dlit, he3d_CVector& pos, DWORD dwColor, FLOAT fRange, FLOAT fAtt0, FLOAT fAtt1, FLOAT fAtt2 )
{
	ZeroMemory( d3dlit, sizeof(D3DLIGHT8) );

	d3dlit->Type			= D3DLIGHT_POINT;

	d3dlit->Attenuation0	= fAtt0;
	d3dlit->Attenuation1	= fAtt1;
	d3dlit->Attenuation2	= fAtt2;

	d3dlit->Range			= fRange;

	d3dlit->Position.x		= pos.x;
	d3dlit->Position.y		= pos.y;
	d3dlit->Position.z		= pos.z;

	d3dlit->Diffuse.a = ( (FLOAT)( ( dwColor >> 24 )&0xff ) )/255.0f;
	d3dlit->Diffuse.r = ( (FLOAT)( ( dwColor >> 16 )&0xff ) )/255.0f;
	d3dlit->Diffuse.g = ( (FLOAT)( ( dwColor >>  8 )&0xff ) )/255.0f;
	d3dlit->Diffuse.b = ( (FLOAT)( ( dwColor >>  0 )&0xff ) )/255.0f;
}